/**

This file is part of MaCI/GIMnet.

MaCI/GIMnet is free software: you can redistribute it and/or modify it 
under the terms of the GNU Lesser General Public License as published 
by the Free Software Foundation, either version 3 of the License, or 
(at your option) any later version.

MaCI/GIMnet is distributed in the hope that it will be useful, but WITHOUT 
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 
FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public 
License for more details.

You should have received a copy of the GNU Lesser General Public 
License along with GIMnet. (See COPYING.LESSER) If not, see 
<http://www.gnu.org/licenses/>.

**/
/**
 * \file
 * \brief Protocol identification structure header.
 * \author Antti Maula <antti.maula@tkk.fi>
 */

#ifndef _PROTOCOL_H_
#define _PROTOCOL_H_
#include "connectionList.h"
#include "protocolID.h"

struct TConnectionList;
struct TConnectionListEntry;

typedef enum { protocolExitNoError = 0,
	       protocolExitIncompleteCommand = 1,
	       protocolExitInvalidCommand = -1,
	       protocolExitError = -2 } EProtocolExit;


typedef EProtocolExit (*protocolRawHandlerPtr)(void *pData, 
                                               TConnectionList *l, 
                                               const unsigned char *data,
                                               int bytes);
typedef EProtocolExit (*protocolHandlerPtr)(void *pData, 
                                            TConnectionList *l, 
                                            TConnectionListEntry *e);
typedef EProtocolExit (*protocolErrorHandlerPtr)(void *pData, 
                                                 TConnectionList *l, 
                                                 TConnectionListEntry *e);

typedef struct _protocolEntry 
{
  unsigned char protocol_number;   ///< Protocol identification number
  unsigned char protocol_version;  ///< Matching version
  
  void *protocolData;                 ///< Pointer to protocolhandler internal data
  protocolRawHandlerPtr protocolRawHandler; ///< Pointer to protocol RAW handler.
  protocolHandlerPtr protocolHandler; ///< Pointer to protocol handler
  protocolErrorHandlerPtr protocolErrorHandler; ///< Pointer to protocol errorhandler
} TProtocolEntry;

typedef struct _protocol {
  const TProtocolEntry *entrytable[MAX_PROTOCOL_COUNT]; ///< Protocol pool
} TProtocol;

int protocolInit();
int protocolDeinit();

void protocolEntryDestroy(TProtocolEntry *pe);
TProtocolEntry *protocolEntryConstructNew(int number,
                                          void *pData,
                                          protocolRawHandlerPtr protocolRawHandler,
                                          protocolHandlerPtr protocolHandler,
                                          protocolErrorHandlerPtr protocolErrorHandler);

void protocolEntryConstruct(TProtocolEntry *pe,
                            int number,
                            void *pData,
                            protocolRawHandlerPtr protocolRawHandler,
                            protocolHandlerPtr protocolHandler,
                            protocolErrorHandlerPtr protocolErrorHandler);

int protocolRegisterProtocol(int protocol_number, const TProtocolEntry *entry);
const TProtocolEntry *protocolGetProtocolEntry(int protocol_number);

#endif

